#ifndef ANGRYBR3DS_H
#define ANGRYBR3DS_H

class btCollisionShape;

#include <vector>

using namespace std;

#include "BulletDynamics/Vehicle/btRaycastVehicle.h"
#include "BulletDynamics/ConstraintSolver/btHingeConstraint.h"
#include "BulletDynamics/ConstraintSolver/btSliderConstraint.h"
#include "BulletSoftBody/btSoftBodyRigidBodyCollisionConfiguration.h"
#include "BulletSoftBody/btSoftBody.h"
#include "LinearMath/btAlignedObjectArray.h"

#ifdef _WIN32
#include "GlutDemoApplication.h"
#else
#include "GL/GlutDemoApplication.h"
#endif //_WINDOWS

#include "Cameras.h"


class AngryBr3ds : public GlutDemoApplication
{
	public:

	struct Brick{
		btRigidBody* body;
		btScalar mass;
		bool hitGround;	
		bool hitBird;
	};

	vector<Brick> bricks;

	Cameras cam;
	
	int points;
	int multiplier;
	int birdsShot;

	bool m_useDefaultCamera;
	float m_cameraHeight;
	float m_minCameraDistance;
	float m_maxCameraDistance;

	int m_lastmousepos[2];
        btVector3 m_impact;
        btSoftBody::sRayCast m_results;
        btSoftBody::Node* m_node;
        btVector3 m_goal;
        bool m_drag;


//----------------------------
	btRigidBody* 	m_slingshot;
	btVector3 	m_slingshotPos;
//----------------------------

	btAlignedObjectArray<btCollisionShape*> m_collisionShapes;
	class btBroadphaseInterface*	m_overlappingPairCache;
	class btCollisionDispatcher*	m_dispatcher;
	class btConstraintSolver*	m_constraintSolver;
	class btSoftBodyRigidBodyCollisionConfiguration* m_collisionConfiguration;
	class btSoftRigidDynamicsWorld* m_softRigidDynamicsWorld;
	btSoftBodyWorldInfo	m_softBodyWorldInfo;


	AngryBr3ds();
	virtual ~AngryBr3ds();
	
	void writeScreenInfo();
	virtual void clientMoveAndDisplay();
	virtual void	clientResetScene();

	virtual void displayCallback();
	
	virtual void updateCamera();

	virtual void specialKeyboard(int key, int x, int y);
	virtual void specialKeyboardUp(int key, int x, int y);
	virtual void mouseMotionFunc(int x,int y);
	virtual void mouseFunc(int button, int state, int x, int y);

	void renderme();

	void initPhysics();
	void termPhysics();

	void createSlingshot(float scale, btVector3 &origin);
	void createNewBird(float scale);
	btRigidBody* createNewBrick(btVector3 &pos, btVector3 &size, btScalar &mass, btVector3 &localInertia);
	btRigidBody* createNewPig(btVector3 &pos, btVector3 &size, btScalar &mass, btVector3 &localInertia);

	void setLevel();

	static DemoApplication* Create()
	{
		AngryBr3ds* demo = new AngryBr3ds();
		demo->myinit();
		demo->initPhysics();
		return demo;
	}

	virtual const btSoftRigidDynamicsWorld* getSoftDynamicsWorld() const
        {
                return (btSoftRigidDynamicsWorld*) m_dynamicsWorld;
        }

        virtual btSoftRigidDynamicsWorld*       getSoftDynamicsWorld()
        {
                return (btSoftRigidDynamicsWorld*) m_dynamicsWorld;
        }
};

#endif // ANGRYBR3DS_H


